package com.jt.www.util.excel;

import com.alibaba.fastjson.JSONObject;
import com.jt.www.util.DateUtils;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang.StringUtils;

import javax.servlet.http.HttpServletResponse;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Map;

/**
 * @Desc 导出csv
 * @Date 2020/3/3 0:10
 * @Author lq
 */
public class CsvExportUtil {
    /**
     * 导出每页最大记录数
     */
    public static final Integer MAX_PAGE_SIZE = 1000;
    /**
     * CSV文件列分隔符
     */
    private static final String CSV_COLUMN_SEPARATOR = ",";
    /**
     * CSV文件行分隔符
     */
    private static final String CSV_ROW_SEPARATOR = System.lineSeparator();
    /**
     * 内容为空默认值
     */
    private static final String CSV_COLUMN_NULL = "-,";

    /**
     * @param dataList 集合数据
     * @param titles   表头部数据
     * @param keys     表内容的键值
     * @param os       输出流
     */
    public static void doExport(List<Map<String, Object>> dataList, String titles, String keys, OutputStream os) throws Exception {

        // 保证线程安全
        StringBuffer buf = new StringBuffer();

        String[] titleArr = null;
        String[] keyArr = null;

        titleArr = titles.split(",");
        keyArr = keys.split(",");

        // 组装表头
        for (String title : titleArr) {
            buf.append(title).append(CSV_COLUMN_SEPARATOR);
        }
        buf.append(CSV_ROW_SEPARATOR);

        // 组装数据
        if (CollectionUtils.isNotEmpty(dataList)) {
            for (Map<String, Object> data : dataList) {
                for (String key : keyArr) {
                    buf.append(data.get(key)).append(CSV_COLUMN_SEPARATOR);
                }
                buf.append(CSV_ROW_SEPARATOR);
            }
        }

        // 写出响应
        os.write(buf.toString().getBytes("GBK"));
        os.flush();
    }

    /**
     * 设置Header
     *
     * @param fileName
     * @param response
     * @throws UnsupportedEncodingException
     */
    public static void responseSetProperties(String fileName, HttpServletResponse response) throws UnsupportedEncodingException {
        // 设置文件后缀
        SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss");
        String fn = fileName + sdf.format(new Date()) + ".csv";
        // 读取字符编码
        String utf = "UTF-8";

        // 设置响应
        response.setContentType("application/ms-txt.numberformat:@");
        response.setCharacterEncoding(utf);
        response.setHeader("Pragma", "public");
        response.setHeader("Cache-Control", "max-age=30");
        response.setHeader("Content-Disposition", "attachment; filename=\"" + URLEncoder.encode(fn, utf) + "\"");
        response.setHeader("Content-Type", "text/csv");
    }

    /**
     * @param titles 表头部数据
     * @param os     输出流
     */
    public static void setTitles(String titles, OutputStream os) throws Exception {
        // 写出响应
        os.write(titles.getBytes("GBK"));
        os.write(CSV_ROW_SEPARATOR.getBytes("GBK"));
        os.flush();
    }

    /**
     * @param dataList 集合数据
     * @param keyArr   表内容的键值
     * @param os       输出流
     */
    public static void doExport(List<? extends Object> dataList, String[] keyArr, OutputStream os) throws Exception {

        // 保证线程安全
        StringBuffer buf = new StringBuffer();
        // 组装数据
        if (CollectionUtils.isNotEmpty(dataList)) {
            for (Object data : dataList) {
                //将object转成map
                Map<String, Object> stringObjectMap = JSONObject.parseObject(JSONObject.toJSONString(data), Map.class);
                // 写出响应
                os.write(handleExportData(stringObjectMap, keyArr).getBytes("GBK"));
                buf.append(CSV_ROW_SEPARATOR);
            }
        }
        os.flush();
    }

    /**
     * 处理下载指标
     */
    public static String handleExportData(Map<String, Object> reportData, String[] columns) {
        StringBuilder sb = new StringBuilder();
        for (String columnName : columns) {
            addStringBuffer(sb, reportData, columnName);
        }
        sb.append(CSV_ROW_SEPARATOR);
        return sb.toString();
    }

    public static void addStringBuffer(StringBuilder sb, Map<String, Object> map, String name) {
        if (map.get(name) == null) {
            sb.append(CSV_COLUMN_NULL);
        } else {
            String value;
            if (map.get(name) instanceof Date) {
                value = DateUtils.format((Date) map.get(name), DateUtils.DATE_TIME_FORMAT_YYYY_MM_DD_HH_MI_SS);
            } else {
                value = String.valueOf(map.get(name));
            }
            String temp = value.replaceAll("\r", "")
                    .replaceAll("\n", "")
                    .replaceAll(",", "、");
            /*if (temp.contains(",")) {
                if (temp.contains("\"")) {
                    temp = temp.replace("\"", "\"\"");
                }
                //将逗号转义
                temp = "\"" + temp + "\"";
            }*/
            sb.append(StringUtils.isNumeric(temp) && temp.length() > 11 ? temp + "\t" : temp).append(CSV_COLUMN_SEPARATOR);
        }
    }

}
